﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web;
using System.Web.Mvc;
using System.Web.Mvc.Ajax;
using System.Web.Routing;
using System.Collections.Specialized;

using Microsoft.Practices.Unity;

using ERPStore.Services;
using ERPStore.Extensions;

using ERPStore.Web.Html;
using ERPStore.Web.Extensions;

using CloudSoft.Extensions;

namespace ERPStore.Web.Controllers
{
	public partial class CatalogController
	{
		[AcceptVerbs(HttpVerbs.Get)]
		[ActionFilters.TrackerActionFilter]
		public ActionResult DirectSearch(string s)
		{
			s = System.Web.HttpUtility.UrlDecode(s);
			return Search(s);
		}

		[AcceptVerbs(HttpVerbs.Get)]
		[ActionFilters.TrackerActionFilter]
		public ActionResult Search(string s)
		{
			if (s.IsNullOrTrimmedEmpty())
			{
				return View("NoProductFound");
			}

			s = s.Trim();
			var substitution = CatalogService.SubstituteSearchTerms(s);
			if (substitution != null)
			{
				switch (substitution.Type)
				{
					case ERPStore.Models.ProductSearchSubstitutionType.Keyword:
						s = substitution.SubstitutionTerm;
						break;
					case ERPStore.Models.ProductSearchSubstitutionType.Variant:
						var product = CatalogService.GetProductByCode(s);
						var url = Url.Href(product);
						return Redirect(url);
					default:
						break;
				}
			}

			var filter = CatalogService.CreateProductListFilter(HttpContext.GetWebContextParameterList());
			filter.SortByScore = Request[GlobalConfiguration.Configuration.Settings.Catalog.PageSortParameterName] == null;
			filter.Search = s;

			var result = GetProductList(filter);
			result.Substitution = substitution;

			if (result.PageIndex == 1)
			{
				EventPublisherService.PublishAsync(new Events.ProductSearchEvent(User, s, result.Count, CatalogService.Name));
				ViewData["search"] = filter.Search;
				ViewData["resultCount"] = result.Count;
			}

			// Dans le cas ou le numéro de page n'exise plus
			// On retourne sur la premiere page 
			if (result != null
				&& result.Count == 0
				&& result.PageIndex > 1)
			{
				var url = Request.RawUrl.RemoveParameter(ERPStore.GlobalConfiguration.Configuration.Settings.Catalog.PageParameterName);
				return Redirect(url);
			}

			if (result.IsNullOrEmpty())
			{
				if (filter.ProductCategoryId.HasValue
					|| filter.BrandId.HasValue)
				{
					filter.ProductCategoryId = null;
					filter.BrandId = null;
					result = GetProductList(filter);
					if (result.IsNullOrEmpty())
					{
						Logger.Warn("no product found for search : {0}\r\n{1}\r\n{2}", s, Request.RawUrl, Request.UserAgent);
						var contactInfo = new ERPStore.Models.ContactInfo();
						ViewData.Model = contactInfo;
						return View("NoProductFound");
					}
				}
				else
				{
					Logger.Warn("no product found for search : {0}\r\n{1}\r\n{2}", s, Request.RawUrl, Request.UserAgent);
					var contactInfo = new ERPStore.Models.ContactInfo();
					ViewData.Model = contactInfo;
					return View("NoProductFound");
				}
			}

			// Afficher directement la fiche produit
			if (result.Count == 1)
			{
				var p = result.First();
				var url = Url.Href(p);
				return Redirect(url);
			}

			result.Query = s;
			result.ListType = ERPStore.Models.ProductListType.Search;

			EventPublisherService.PublishAsync(new Events.ProductListEvent(User, result, ERPStore.Models.ProductListType.Search));

			ViewBag.ProductListFilter = filter;
			ViewData.Model = result;
			return View("ProductSearchResult");
		}

		#region Partial Render

		[HttpGet]
		public ActionResult ShowContinuousSearchResult()
		{
			return new EmptyResult();
		}

		[ActionFilters.TrackerActionFilter]
		[HttpPost]
		public ActionResult ShowContinuousSearchResult(string filter, int pageIndex, string viewName)
		{
			if (filter == null)
			{
				return new EmptyResult();
			}

			var jsonfilter = filter.UnGZipFromBase64String();
			var f = jsonfilter.FromJSon<ERPStore.Models.ProductListFilter>();

			var result = GetProductList(f, -1, pageIndex);

			if (result.IsNullOrEmpty())
			{
				return new EmptyResult();
			}

			result.Query = f.Search;
			result.ListType = ERPStore.Models.ProductListType.Search;
			EventPublisherService.PublishAsync(new Events.ProductListEvent(User, result, ERPStore.Models.ProductListType.Search));

			ViewBag.ProductListFilter = filter;
			ViewData.Model = result;
			return PartialView(viewName);
		}

		// [ActionFilters.CacheActionFilter(CacheKey="ShowTopSearchTermList", Duration=3600, VaryByParam="*")]
		public ActionResult ShowTopSearchTermList(string viewName, int count)
		{
			var list = CatalogService.GetTopSearchTermList(count);
			ViewData.Model = list;
			return PartialView(viewName);
		}

		#endregion

	}
}
